var wuenas;
$(document).ready(function(){
	wuenas = new Wuenas(false, 1500);
});

//Wuenas functions
function Wuenas(isAutoScan, autoScanInterval){
	//Markup properties
	this.componentClass = "wu-component";
	this.actionClass = "wu-action";
	this.firstFocusClass = "wu-focus";
	this.autoFocusClass = "wu-autofocus";
	this.formClass = "wu-form";

	//Basic Elements
	this.outerContainer = document;
	this.focusedElement;

	//Autoscan properties
	this.autoScanner = new WuenasAutoScanner(this, autoScanInterval);
	this.isAutoScan = isAutoScan;
	 
	//Keyboard properties
	this.keyboard = new WuenasKeyboard(this);
	 
	this.init = function(){
		
		this.keydownCapture();
		
		// Setting tabindex="0" in all components and actions allows js to use focus() funcion on them.
		$("."+this.componentClass+", ."+this.actionClass, $(this.outerContainer)).attr("tabindex","0");
		//Setting focus on th 
		this.firstFocus();
		
		if(this.isAutoScan){
			this.autoScanner.start();
		}
		
		
	};
	this.keydownCapture = function(){
		//Keydown capture
		var self = this;
		$(this.outerContainer).keydown(function(event){
			//Allow Refresh on F5
			if(event.which == "116")
				return true;
			event.preventDefault();
			event.stopPropagation();
			//Events
			//1. Next
			if(event.which == "9"/*Tab*/){
				self.next();
			}
			//2. Enter
			else if(event.which == "13"/*Enter*/){
				self.enter();
			}
			//3. Back
			else if(event.which == "8"/*Backspace*/){
				self.back();
			}
		});
	};
	this.firstFocus = function(){
		if($("."+this.firstFocusClass, $(this.outerContainer)).length > 0){
			$("."+this.firstFocusClass+":first", $(this.outerContainer)).focus();
		}else{
			$("."+this.componentClass+":first", $(this.outerContainer)).focus();
		}
	   
	};
	this.next = function(){
	   	if($(":focus", $(this.outerContainer)).length == 0){
	   		this.firstFocus();
	   	}else{
	   		this.focusedElement = $(":focus", $(this.outerContainer));
	   		
	   		var clazz;
	   		if(this.focusedElement.hasClass(this.componentClass)){
	   			clazz = this.componentClass;
	   		}else if (this.focusedElement.hasClass(this.actionClass)){
	   			clazz = this.actionClass;
	   		}else{
	   			this.firstFocus();
	   			return;
	   		}
	   		
	   		var parents = $(this.focusedElement).parents("."+this.componentClass, $(this.outerContainer));
			//Select the "components" or "actions" inside the same parent "component" pai, but the "components"/"actions" in deeper levels 
			var levelSelector = "";
			for(var j = 0; j <= parents.length; j++) levelSelector += " ."+this.componentClass;
			//levelSelector = " ."+clazz+":visible:not("+levelSelector+" ."+this.componentClass+" ."+clazz+")";
			levelSelector += " *";
			
			var parentComponent;
			if(parents.length == 0) parentComponent = this.outerContainer;
			else parentComponent = parents.get(0);

			var children = $(parentComponent).find("."+this.componentClass+":visible, ."+this.actionClass+":visible").not(levelSelector);
			
			var focusTarget = null;
			var indexOfThis = jQuery.inArray(this.focusedElement.get(0), children);
			if(indexOfThis == children.length - 1){
				focusTarget = children[0];
			}else{
				focusTarget = children[indexOfThis+1];
			}
			if($(focusTarget).hasClass(this.autoFocusClass)){
				focusTarget = $(focusTarget).find(this.componentClass+","+this.actionClass)[0];
			}
			$(focusTarget).focus();	
	   	}			
   				
	};
   this.enter = function(){
   		this.focusedElement = $(":focus", $(this.outerContainer));
   		if(this.focusedElement.hasClass(this.componentClass)){
   			$(this.focusedElement.find("."+this.componentClass+":visible, ."+this.actionClass+":visible", $(this.outerContainer))[0]).focus();
   			
   		}else if (this.focusedElement.hasClass(this.actionClass)){
	   		if(this.focusedElement.prop("tagName").toLowerCase() == "input" && this.focusedElement.attr("type").toLowerCase() == "text"){
   				this.keyboard.appear(this.focusedElement);
	   		}else if(this.focusedElement.prop("tagName").toLowerCase() == "select"){
	   			new WuenasSelect(this, this.focusedElement);
	   		}else
   				this.focusedElement.click();
	   	}
	   	if(this.isAutoScan){
			this.autoScanner.start();
		}
   	};
   	this.back = function(){
		this.focusedElement = $(":focus", $(this.outerContainer));   			
   		
   		var el = $(this.focusedElement.parents("."+this.componenteClass)[0], $(this.outerContainer))[0];
   		
   		var parents = $(this.focusedElement).parents("."+this.componentClass, $(this.outerContainer));
		if(parents.length == 0){
			this.firstFocus();
		}else {
			$(parents.get(0)).focus();
		}
		if(this.isAutoScan){
			this.autoScanner.start();
		}
   };
   this.init();
}

function WuenasAutoScanner(wuenas, interval){
	this.timerAlias = "wu_scan_timer";
	this.wuenasInstance = wuenas;
	this.interval = interval;
	
	this.start = function(){
	   this.stop();
		$(this).everyTime(this.interval, this.timerAlias, function() {
		    this.wuenasInstance.next();
		});
		this.wuenasInstance.isAutoScan = true;
	};
	this.stop = function(){
	   $(this).stopTime(this.timerAlias);
	   this.wuenasInstance.isAutoScan = false;
	};
}
